.Dd $Mdocdate: February 16 2015 $
.Dt BIO_PUSH 3
.Os
.Sh NAME
.Nm BIO_push ,
.Nm BIO_pop
.Nd add and remove BIOs from a chain
.Sh SYNOPSIS
.In openssl/bio.h
.Ft BIO *
.Fo BIO_push
.Fa "BIO *b"
.Fa "BIO *append"
.Fc
.Ft BIO *
.Fo BIO_pop
.Fa "BIO *b"
.Fc
.Sh DESCRIPTION
The
.Fn BIO_push
function appends the BIO
.Fa append
to
.Fa b
and returns
.Fa b .
.Pp
.Fn BIO_pop
removes the BIO
.Fa b
from a chain and returns the next BIO in the chain, or
.Dv NULL
if there is no next BIO.
The removed BIO then becomes a single BIO with no association with the
original chain, it can thus be freed or attached to a different chain.
.Sh RETURN VALUES
.Fn BIO_push
returns the beginning of the chain,
.Fa b .
.Pp
.Fn BIO_pop
returns the next BIO in the chain, or
.Dv NULL
if there is no next BIO.
.Sh NOTES
The names of these functions are perhaps a little misleading.
.Fn BIO_push
joins two BIO chains whereas
.Fn BIO_pop
deletes a single BIO from a chain,
the deleted BIO does not need to be at the end of a chain.
.Pp
The process of calling
.Fn BIO_push
and
.Fn BIO_pop
on a BIO may have additional consequences:
a control call is made to the affected BIOs.
Any effects will be noted in the descriptions of individual BIOs.
.Sh EXAMPLES
For these examples suppose
.Sy md1
and
.Sy md2
are digest BIOs,
.Sy b64
is a base64 BIO and
.Sy f
is a file BIO.
.Pp
If the call
.Pp
.Dl BIO_push(b64, f);
.Pp
is made then the new chain will be
.Sy b64-f .
After making the calls
.Bd -literal -offset indent
BIO_push(md2, b64);
BIO_push(md1, md2);
.Ed
.Pp
the new chain is
.Sy md1-md2-b64-f .
Data written to
.Sy md1
will be digested
by
.Sy md1
and
.Sy md2 ,
.Sy base64
encoded and written to
.Sy f .
.Pp
It should be noted that reading causes data to pass
in the reverse direction, that is data is read from
.Sy f ,
base64
.Sy decoded
and digested
by
.Sy md1
and
.Sy md2 .
If this call is made:
.Pp
.Dl BIO_pop(md2);
.Pp
The call will return
.Sy b64
and the new chain will be
.Sy md1-b64-f Ns ;
data can be written to
.Sy md1
as before.
